home *** CD-ROM | disk | FTP | other *** search
/ HPAVC / HPAVC CD-ROM.iso / INTER53E.ZIP / INTLIST.E < prev    next >
Text File  |  1997-01-12  |  43KB  |  1,502 lines

  1. /****************************************************************/
  2. /*    EEL code file for editing the Interrupt List        */
  3. /*                                */
  4. /*    Written by Ralf Brown                    */
  5. /*    LastEdit:  12 Jan 97                    */
  6. /*                                */
  7. /*  This EEL file adds the following keybindings:        */
  8. /*    Shf-Alt-A add an Access: section to the current entry    */
  9. /*    Shf-Alt-B add another BUG: to the current entry           */
  10. /*    Shf-Alt-D add a Desc: section to the current entry    */
  11. /*    Sft-Alt-I add an InstallCheck: section to current entry    */
  12. /*    Shf-Alt-R add a Range: section to the current entry       */
  13. /*    Shf-Alt-S add a Size: section to the current entry    */
  14. /*    Alt-I    add an Index: section to the current entry    */
  15. /*        add another Index: line if already on Index:    */
  16. /*      Alt-N   add a new note to current entry or data struct  */
  17. /*      Alt-P   add a Program: section to the current entry     */
  18. /*      Alt-R   insert Return: at start of line                 */
  19. /*    Alt-S    insert SeeAlso: at start of line        */
  20. /*    F11    insert a blank separator line            */
  21. /*    ^F11    create Format of: header            */
  22. /*    Shf-F11    create Values for: header            */
  23. /*    Alt-F11 create Call with: header            */
  24. /*    Alt-F12 create Bitfield for: header            */
  25. /*    F12    add the interrupt number to the separator line    */
  26. /*        preceding the current entry            */
  27. /*    ^F12    jump to a specified entry            */
  28. /*                                */
  29. /*  It adds the following unbound commands:                */
  30. /*      renumber-tables                            */
  31. /*    make-distribution                    */
  32. /*                                */ 
  33. /*  Other:                            */
  34. /*    adds intlist-mode for .LST and .1ST files        */
  35. /*    switches current buffer into intlist-mode on loading    */
  36. /*      maintains a table counter which is inserted each time   */
  37. /*        a table is created in the text                */
  38. /*      performs syntax highlighting (Epsilon v7+)        */
  39. /****************************************************************/
  40.  
  41. #include "eel.h"
  42. #if EELVERSION >= 70
  43. #include "colcode.h"
  44. #endif /* Epsilon v7.0+ */
  45.  
  46. keytable intlist_tab ;            /* key table for IntList mode */
  47.  
  48. /* on repeated F12, how often to display number of entries processed */
  49. /* for fast 386, every 100; for a Pentium, at least 300 or the message */
  50. /* line will lag way behind the actual progress */
  51. #define NUMBER_INT_PROGRESS_INTERVAL 500
  52.  
  53. /*=============================================================*/
  54. /*    Global Variables                           */
  55. /*=============================================================*/
  56.  
  57. /* table headings */
  58. char str_format_of[] = "Format of " ;
  59. char str_bitfields_for[] = "Bitfields for " ;
  60.  
  61. /* section names within an entry */
  62. char size_section[] = "Size:\t" ;
  63. char access_section[] = "Access:\t" ;
  64. char return_section[] = "Return: " ;
  65. char install_section[] = "InstallCheck:\t" ;
  66. char program_section[] = "Program: " ;
  67. char desc_section[] = "Desc:\t" ;
  68. char range_section[] = "Range:\t" ;
  69. char notes_section[] = "Notes*:\t" ;
  70. char bugs_section[] = "BUGS*:\t" ;
  71. char example_section[] = "Example: " ;
  72. char seealso_section[] = "SeeAlso: " ;
  73. char index_section[] = "Index:\t" ;
  74.  
  75. #if EELVERSION >= 70
  76. char all_sections[] = "Return:|SeeAlso:|Program:|Desc:|Range:|Notes*:|BUGS*:|Example:|Index:|Access:|InstallCheck:|Size:" ;
  77. char indented_sections[] = "[\t ]*(Return|Notes*):" ;
  78. char table_headers[] = "INT |MEM |CMOS |MSR |CALL |PORT |Format |Values |Bitfields |Call " ;
  79. #endif /* Epsilon v7.0+ */
  80.  
  81. char table_ID_letters[] = "0123456789CFMPR" ;
  82.  
  83. char *(section_order[13]) ;
  84. char *(list_files[10]) ;
  85.  
  86. when_loading()
  87. {
  88.    /* list the sections of an entry in the order they should appear (if */
  89.    /* present at all) */
  90.    section_order[0] = size_section ;
  91.    section_order[1] = access_section ;
  92.    section_order[2] = return_section ;
  93.    section_order[3] = install_section ;
  94.    section_order[4] = program_section ;
  95.    section_order[5] = desc_section ;
  96.    section_order[6] = range_section ;
  97.    section_order[7] = notes_section ;
  98.    section_order[8] = bugs_section ;
  99.    section_order[9] = example_section ;
  100.    section_order[10] = seealso_section ;
  101.    section_order[11] = index_section ;
  102.    section_order[12] = NULL ;
  103.    /* list the files comprising the full interrupt list */
  104.    list_files[0] = "cmos.lst" ;
  105.    list_files[1] = "farcall.lst" ;
  106.    list_files[2] = "memory.lst" ;
  107.    list_files[3] = "ports.lst" ;
  108.    list_files[4] = "interrup.lst" ;
  109.    list_files[5] = "tables.lst" ;
  110.    list_files[6] = "msr.lst" ;
  111.    list_files[7] = "biblio.lst" ;
  112.    list_files[8] = "glossary.lst" ;
  113.    list_files[9] = NULL ;
  114. }
  115.  
  116. /*=============================================================*/
  117. /*    Buffer-specific variables                       */
  118. /*=============================================================*/
  119.  
  120. buffer spot table_counter ;
  121.  
  122. /*=============================================================*/
  123. /*=============================================================*/
  124.  
  125. int empty_line()
  126. {
  127.    return (character(point-1) == '\n' && character(point) == '\n') ;
  128. }
  129.  
  130. /*=============================================================*/
  131. /*=============================================================*/
  132.  
  133. int is_separator_line()
  134. {
  135.    return (empty_line() || parse_string(1,"--------",NULL)) ;
  136. }
  137.  
  138. /*=============================================================*/
  139. /* search in the specified direction (1 = forward, -1 = back)  */
  140. /* for the next entry separator line                   */
  141. /*=============================================================*/
  142.  
  143. int to_separator_line(dir)
  144. int dir ;
  145. {
  146.    nl_reverse() ;
  147.    return search(dir,"\n--------") ;
  148. }
  149.  
  150. /*=============================================================*/
  151. /* move to the location where the specified section of an      */
  152. /* entry begins (if present) or should begin (if not)           */
  153. /*=============================================================*/
  154.  
  155. int to_section_start(section)
  156. char *section ;
  157. {
  158.    int i, j, len ;
  159.  
  160.    for (i = 0 ; section_order[i] ; i++)
  161.       if (strcmp(section,section_order[i]) == 0)
  162.      break ;
  163.    if (section_order[i])
  164.       {
  165.       while (!is_separator_line())
  166.      {
  167.      for (j = i ; section_order[j] ; j++)
  168.         if (parse_string(1,section_order[j],NULL))
  169.            {
  170.            if ((len = parse_string(1,section,NULL)) != 0)
  171.           {
  172.           point += len ;
  173.           return 1 ;    /* section already exists */
  174.           }
  175.            return 0 ;    /* section nonexistent, but found position */
  176.            }
  177.      if (!nl_forward())
  178.         break ;
  179.      }
  180.       return 0 ;    /* section does not yet exist */
  181.       }
  182.    else
  183.       return 0 ;    /* section not found */
  184. }
  185.  
  186. /*=============================================================*/
  187. /*=============================================================*/
  188.  
  189. int make_section(section,start_entry,name)
  190. char *section, *name ;
  191. int start_entry ;
  192. {
  193.    int start = point ;
  194.  
  195.    if (start_entry)
  196.       {
  197.       if (!to_separator_line(-1))  /* find previous separator line */
  198.      {
  199.      point = start ;
  200.      say("Not in an interrupt entry") ;
  201.      return 0 ;
  202.      }
  203.       }
  204.    else
  205.       {
  206.       to_begin_line() ;
  207.       while (!empty_line() && !parse_string(1,"\n--------",NULL))
  208.      if (!nl_reverse())
  209.         break ;
  210.       }
  211.    point++ ;                 /* skip the newline */
  212.    nl_forward() ;             /* advance to first line of entry */
  213.    if (!to_section_start(section))
  214.       {
  215.       if (name)
  216.      stuff(name) ;
  217.       else
  218.      stuff(section) ;
  219.       stuff("\n") ;
  220.       point-- ;              /* back up over inserted newline */
  221.       return 1 ;
  222.       }
  223.    else
  224.       return 0 ;
  225.    return 2 ;  /* just in case */
  226. }
  227.  
  228. /*=============================================================*/
  229. /*=============================================================*/
  230.  
  231. int pluralize_section(plural)
  232. char plural ;
  233. {
  234.    point -= 3 ;
  235.    if (curchar() != plural)        /* already plural ? */
  236.       {
  237.       point++ ;
  238.       insert(plural) ;
  239.       }
  240.    nl_forward() ;
  241.    while (!is_separator_line() && parse_string(1,"[ \t]",NULL))
  242.       nl_forward() ;
  243.    stuff("\t\n") ;
  244.    point-- ;
  245. }
  246.  
  247. /*=============================================================*/
  248. /* Add "SeeAlso: " to the beginning of the current line unless */
  249. /* it is already present; in that case, insert a fresh line    */
  250. /* containing just a SeeAlso: and position the cursor at the   */
  251. /* end of the new line                           */
  252. /*=============================================================*/
  253.  
  254. command see_also() on intlist_tab[ALT('s')]
  255. {
  256.    to_begin_line() ;
  257.    if (parse_string(1,"SeeAlso: ",NULL) == 0)
  258.       stuff("SeeAlso: ") ;
  259.    else
  260.       {
  261.       nl_forward() ;
  262.       stuff("SeeAlso: \n") ;
  263.       point-- ;
  264.       }
  265. }
  266.  
  267. /*=============================================================*/
  268. /* Add a Desc: section if the current entry does not already   */
  269. /* have one; if there is already a Desc: section, move to the  */
  270. /* start of it                               */
  271. /*=============================================================*/
  272.  
  273. command access() on intlist_tab[ALT('A')]
  274. {
  275.    make_section(access_section,1,NULL) ;
  276. }
  277.  
  278. /*=============================================================*/
  279. /* Add a Desc: section if the current entry does not already   */
  280. /* have one; if there is already a Desc: section, move to the  */
  281. /* start of it                               */
  282. /*=============================================================*/
  283.  
  284. command desc() on intlist_tab[ALT('D')]
  285. {
  286.    make_section(desc_section,1,NULL) ;
  287. }
  288.  
  289. /*=============================================================*/
  290. /* Add a InstallCheck: section if the current entry does not   */
  291. /* already have one; if there is already a InstallCheck:       */
  292. /* section, move to the start of it                   */
  293. /*=============================================================*/
  294.  
  295. command instcheck() on intlist_tab[ALT('I')]
  296. {
  297.    make_section(install_section,1,NULL) ;
  298. }
  299.  
  300. /*=============================================================*/
  301. /* Add a Range: section if the current entry does not already  */
  302. /* have one; if there is already a Range: section, move to the */
  303. /* start of it                               */
  304. /*=============================================================*/
  305.  
  306. command range() on intlist_tab[ALT('R')]
  307. {
  308.    make_section(range_section,1,NULL) ;
  309. }
  310.  
  311. /*=============================================================*/
  312. /* Add a Size: section if the current entry does not already   */
  313. /* have one; if there is already a Size: section, move to the  */
  314. /* start of it                               */
  315. /*=============================================================*/
  316.  
  317. command memsize() on intlist_tab[ALT('S')]
  318. {
  319.    make_section(size_section,1,NULL) ;
  320. }
  321.  
  322. /*=============================================================*/
  323. /* Add a "Program: " section to the current entry if it does   */
  324. /* not have one; otherwise, move to the beginning of the       */
  325. /* Program: section                           */
  326. /*=============================================================*/
  327.  
  328. command program() on intlist_tab[ALT('p')]
  329. {
  330.    make_section(program_section,1,NULL) ;
  331. }
  332.  
  333. /*=============================================================*/
  334. /* Add an "Index: " section to the current entry if it does    */
  335. /* not have one; otherwise, move to the beginning of the       */
  336. /* Index: section                           */
  337. /*=============================================================*/
  338.  
  339. command add_index() on intlist_tab[ALT('i')]
  340. {
  341.    to_begin_line() ;
  342.    if (parse_string(1,"Index:",NULL))
  343.       {
  344.       while (parse_string(1,"Index:",NULL))
  345.      nl_forward() ;
  346.       stuff("Index:\t\n") ;
  347.       point-- ;
  348.       }
  349.    else
  350.       make_section(index_section,1,NULL) ;
  351. }
  352.  
  353. /*=============================================================*/
  354. /*=============================================================*/
  355.  
  356. command bug() on intlist_tab[ALT('B')]
  357. {
  358.    if (!make_section(bugs_section,1,"BUG:\t"))
  359.       pluralize_section('S') ;
  360. }
  361.  
  362. /*=============================================================*/
  363. /* Add "Note: " section to the current entry; change an        */
  364. /* existing Note: to Notes: and position at end of Note:       */
  365. /* section.                               */
  366. /*=============================================================*/
  367.  
  368. command add_note() on intlist_tab[ALT('n')]
  369. {
  370.    if (!make_section(notes_section,0,"Note:\t"))
  371.       pluralize_section('s') ;
  372. }
  373.  
  374. /*=============================================================*/
  375. /* Insert "Return: " at the beginning of the current line, if  */
  376. /* not already present                           */
  377. /*=============================================================*/
  378.  
  379. command returns() on intlist_tab[ALT('r')]
  380. {
  381.    int start = point ;
  382.    
  383.    to_begin_line() ;
  384.    if (parse_string(1,return_section,NULL) == 0)
  385.       stuff(return_section) ;
  386.    else
  387.       point = start ;
  388. }
  389.  
  390. /*=============================================================*/
  391. /* insert a line of dashes prior to the current cursor line    */
  392. /*=============================================================*/
  393.  
  394. command separator_line() on intlist_tab[FKEY(11)]
  395. {
  396.    int i ;
  397.  
  398.    to_begin_line() ;
  399.    for (i = 0 ; i < 45 ; i++)
  400.       insert('-') ;
  401.    insert('\n') ;
  402. }
  403.  
  404. /*=============================================================*/
  405. /*=============================================================*/
  406.  
  407. void insert_table_counter()
  408. {
  409.    char counter[6] ;
  410.    save_var point = *table_counter + 3 ;
  411.  
  412.    /* increment that table counter */
  413.    while (curchar() >= '0')
  414.       {
  415.       if (curchar() < '9')
  416.      {
  417.      replace(point,curchar()+1) ;
  418.      break ;
  419.      }
  420.       else
  421.      {
  422.      replace(point,'0') ;
  423.      point-- ;
  424.      }
  425.       }
  426.    restore_vars() ;
  427.    /* and now insert the incremented value at point */
  428.    stuff("(Table ") ;
  429.    grab(*table_counter,*table_counter+4,counter) ;
  430.    stuff(counter) ;
  431.    stuff(")") ;
  432. }
  433.  
  434. /*=============================================================*/
  435. /* type the name of a structure, then invoke this function     */
  436. /* to create the "Format of X:" and "Offset Size Descr" lines  */
  437. /*=============================================================*/
  438.  
  439. command structure_header() on intlist_tab[FCTRL(11)]
  440. {
  441.    int start = point ;
  442.  
  443.    to_begin_line() ;
  444.    if (parse_string(1,str_format_of,NULL) == 0)
  445.       {
  446.       stuff(str_format_of) ;
  447.       to_end_line() ;
  448.       stuff(":\nOffset\tSize\tDescription\t") ;
  449.       insert_table_counter() ;
  450.       stuff("\n 00h\t") ;
  451.       }
  452.    else
  453.       point = start ;
  454. }
  455.  
  456. /*=============================================================*/
  457. /* Turn the current line into the header for a "Values of"     */
  458. /* section                               */
  459. /*=============================================================*/
  460.  
  461. command value_header() on intlist_tab[FSHIFT(11)]
  462. {
  463.    int start = point ;
  464.    
  465.    to_begin_line() ;
  466.    if (parse_string(1,"Values for ",NULL) == 0)
  467.       {
  468.       insert_table_counter() ;
  469.       stuff("\nValues for ") ;
  470.       to_end_line() ;
  471.       stuff(":\n ") ;
  472.       }
  473.    else
  474.       point = start ;
  475. }
  476.  
  477. /*=============================================================*/
  478. /* Turn the current line into the header of a "Call with"      */
  479. /* section                               */
  480. /*=============================================================*/
  481.  
  482. command call_with_header() on intlist_tab[FALT(11)]
  483. {
  484.    int start = point ;
  485.    
  486.    to_begin_line() ;
  487.    if (parse_string(1,"Call ",NULL) == 0)
  488.       {
  489.       insert_table_counter() ;
  490.       stuff("\nCall ") ;
  491.       to_end_line() ;
  492.       if (character(point-1) != ' ')
  493.      stuff(" ") ;
  494.       stuff("with:\n") ;
  495.       }
  496.    else
  497.       point = start ;
  498. }
  499.  
  500. /*=============================================================*/
  501. /* Turn the current line into the header of a "Bitfield for"   */
  502. /* section                               */
  503. /*=============================================================*/
  504.  
  505. command bitfields_for_header() on intlist_tab[FALT(12)]
  506. {
  507.    int start = point ;
  508.    
  509.    to_begin_line() ;
  510.    if (parse_string(1,str_bitfields_for,NULL) == 0)
  511.       {
  512.       stuff(str_bitfields_for) ;
  513.       to_end_line() ;
  514.       stuff(":\nBit(s)\tDescription\t") ;
  515.       insert_table_counter() ;
  516.       stuff("\n ") ;
  517.       }
  518.    else
  519.       point = start ;
  520. }
  521.  
  522. /*=============================================================*/
  523. /*=============================================================*/
  524.  
  525. char grab_int_entry_number(func_num)
  526. char *func_num ;
  527. {
  528.    int i ;
  529.    char c ;
  530.    
  531.    point += 4 ;                /* skip the "INT " */
  532.    func_num[0] = curchar() ;        /* grab the interrupt number */
  533.    point++ ;
  534.    func_num[1] = curchar() ;
  535.    nl_forward() ;            /* skip to second line of entry */
  536.    if (parse_string(1,"[ \t]*A[LHX][ \t]=[ \t][0-9A-F][0-9A-F]+h",NULL))
  537.       {
  538.       re_search(1,"[ \t]*A") ;
  539.       c = curchar() ;
  540.       point += 4 ;            /* skip ch and " = " */
  541.       if (c != 'L')
  542.      {
  543.      grab(point,point+((c=='X')?4:2),func_num+2) ;
  544.      point += ((c=='X')?4:2) ;
  545.      func_num[(c=='H')?4:6] = '-' ;    /* grab() stuck a NUL into the string */
  546.      }
  547.       else /* c == 'L' */
  548.      {
  549.      func_num[4] = curchar() ;
  550.      point++ ;
  551.      func_num[5] = curchar() ;
  552.      point ++ ;
  553.      }
  554.       point++ ;
  555.       if (parse_string(1,"[ \t]*subfn [0-9A-F][0-9A-F]+h",NULL))
  556.      {
  557.      re_search(1,"[ \t]*subfn ") ;
  558.      func_num[6] = 'S' ;
  559.      func_num[7] = 'F' ;
  560.      for (i = 0 ; i < 4 ; i++)
  561.         {
  562.         c = curchar() ;
  563.         if ((c >= '0' && c <= '9') || (c >= 'A' && c <= 'F'))
  564.            {
  565.            func_num[8+i] = c ;
  566.            point++ ;
  567.            }
  568.         else
  569.            break ;
  570.         }
  571.      }
  572.       nl_forward() ;            /* skip to third line of entry */
  573.       }
  574.    if (parse_string(1,"[ \t]*([BCDES][HILPSX]|VXD) = [0-9A-F][0-9A-F]+h",NULL))
  575.       {
  576.       re_search(1,"[ \t]*") ;
  577.       func_num[6] = curchar() ;
  578.       point++ ;
  579.       func_num[7] = c = curchar() ;
  580.       point += 4 ;            /* skip curchar and " = " */
  581.       if (func_num[6] == 'V')        /* VxD has three letters not two... */
  582.      point++ ;
  583.       if (c == 'H' || c == 'L')
  584.      {
  585.      grab(point,point+2,func_num+8) ;
  586.      func_num[10] = '-' ;        /* grab() stuck a NUL into the string */
  587.      }
  588.       else /* c == 'X' || c == 'I' || c == 'P' || c == 'S' */
  589.      grab(point,point+4,func_num+8) ;
  590.       }
  591.    return 1 ;                /* successful and have func number */
  592. }
  593.  
  594. /*=============================================================*/
  595.  
  596. char grab_cmos_entry_number(func_num)
  597. char *func_num ;
  598. {
  599.    point += 5 ;                    /* skip the "CMOS " */
  600.    func_num[0] = 'R' ;            /* mark this as a CMOS RAM entry */
  601.    grab(point,point+4,func_num+1) ;
  602.    if (func_num[3] == 'h' && func_num[4] == '-')
  603.       grab(point+4,point+6,func_num+3) ;
  604.    else
  605.       {
  606.       func_num[3] = '-' ;
  607.       func_num[4] = '-' ;
  608.       }
  609.    func_num[5] = '-' ;            /* grab() stuck a NUL into string */
  610.    return 1 ;
  611. }
  612.  
  613. /*=============================================================*/
  614.  
  615. char grab_farcall_entry_number(func_num)
  616. char *func_num ;
  617. {
  618.    point += 5 ;                /* skip the "CALL " */
  619.    func_num[0] = '@' ;            /* mark this as a far call entry */
  620.    grab(point,point+4,func_num+1) ;    /* get segment of address */
  621.    grab(point+6,point+10,func_num+5) ;    /* get offset of address */
  622.    func_num[9] = '-' ;            /* grab() stuck a NUL into string */
  623.    return 1 ;
  624. }
  625.  
  626. /*=============================================================*/
  627.  
  628. char grab_msr_entry_number(func_num)
  629. char *func_num ;
  630. {
  631.    point += 4 ;                /* skip the "MSR " */
  632.    func_num[0] = 'S' ;            /* mark this as an MSR entry */
  633.    grab(point,point+8,func_num+1) ;     /* get the MSR number */
  634.    func_num[9] = '-' ;                  /* grab() stuck a NUL into string */
  635.    return 1 ;
  636. }
  637.  
  638. /*=============================================================*/
  639.  
  640. char grab_memory_entry_number(func_num)
  641. char *func_num ;
  642. {
  643.    point += 4 ;                /* skip the "MEM " */
  644.    func_num[0] = 'M' ;                /* mark this as a memory loc entry */
  645.    grab(point,point+6,func_num+1) ;    /* get segment or high word of addr */
  646.    if (func_num[5] == 'h' && func_num[6] == ':') /* segmented address? */
  647.       grab(point+6,point+10,func_num+5) ;    /* get offset of address */
  648.    else
  649.       {
  650.       grab(point+6,point+8,func_num+7) ;/* get low word of the address */
  651.       func_num[0] = 'm' ;        /* indicate linear address */
  652.       }
  653.    func_num[9] = '-' ;            /* grab() stuck a NUL into string */
  654.    return 1 ;
  655. }
  656.  
  657. /*=============================================================*/
  658.  
  659. char grab_port_entry_number(func_num)
  660. char *func_num ;
  661. {
  662.    point += 5 ;                /* skip the "PORT " */
  663.    func_num[0] = 'P' ;            /* mark this as an I/O port entry */
  664.    grab(point,point+4,func_num+1) ;    /* get starting port number */
  665.    func_num[5] = '-' ;            /* grab() stuck a NUL into string */
  666.    if (character(point+4) == '-')
  667.       {
  668.       grab(point+5,point+9,func_num+5) ; /* get ending port number */
  669.       func_num[9] = '-' ;        /* grab() stuck a NUL into string */
  670.       }
  671.    return 1 ;
  672. }
  673.  
  674. /*=============================================================*/
  675.  
  676. char grab_entry_number(func_num)
  677. char *func_num ;
  678. {
  679.    strcpy(func_num,"------------") ;    /* 12 dashes */
  680.    point++ ;                /* go to first char of separator line */
  681.    nl_forward() ;            /* go to first line of entry */
  682.    if (parse_string(1,"INT ",NULL))    /* is it an interrupt entry? */
  683.       return grab_int_entry_number(func_num) ;
  684.    else if (parse_string(1,"CMOS ",NULL) != 0)
  685.       return grab_cmos_entry_number(func_num) ;
  686.    else if (parse_string(1,"CALL ",NULL) != 0)
  687.       return grab_farcall_entry_number(func_num) ;
  688.    else if (parse_string(1,"MEM ",NULL) != 0)
  689.       return grab_memory_entry_number(func_num) ;
  690.    else if (parse_string(1,"PORT ",NULL) != 0)
  691.       return grab_port_entry_number(func_num) ;
  692.    else if (parse_string(1,"MSR ",NULL) != 0)
  693.       return grab_msr_entry_number(func_num) ;
  694.    else
  695.       return 0 ;
  696. }
  697.  
  698. /*=============================================================*/
  699. /* Put the interrupt and function number into the separator    */
  700. /* line just above the intlist entry preceding the cursor pos  */
  701. /*=============================================================*/
  702.  
  703. int number_one_int()
  704. {
  705.    char func_num[13] ;            /* 2->int, 4->AX, 6->extra reg, NUL */
  706.    int oldpoint ;
  707.    
  708.    while (to_separator_line(-1))    /* find previous separator line */
  709.       {
  710.       oldpoint = point ;
  711.       if (grab_entry_number(func_num))    /* does it belong to an intlist entry? */
  712.      {                /*   if yes, success, else try again */
  713.      point = oldpoint + 11 ;    /* skip NL and first ten dashes */
  714.      delete(point,point+12) ;    /* replace 12 dashes by the function */
  715.      stuff(func_num) ;        /*   number and extra register */
  716.      point = oldpoint + 9 ;        /* back to category letter position */
  717.      return 1 ;
  718.      }
  719.       point = oldpoint ;
  720.       }
  721.    return 0 ;                /* if we get here, we failed */
  722. }
  723.  
  724. /*=============================================================*/
  725. /* Put the interrupt and function number into the separator    */
  726. /* line just above one or more intlist entries preceding the   */
  727. /* current cursor position, letting user know of progress      */
  728. /*=============================================================*/
  729.  
  730. command number_int() on intlist_tab[FKEY(12)]
  731. {
  732.    int i, hit_top = 0 ;
  733.    
  734.    for (i = 0 ; i < iter ; i++)
  735.       {
  736.       if (!number_one_int())
  737.      {
  738.      hit_top = 1 ;
  739.      say("No prior entry.") ;
  740.      break ;
  741.      }
  742.       if (((i+1) % NUMBER_INT_PROGRESS_INTERVAL) == 0)
  743.      say("%4d...",i+1) ;
  744.       }
  745.    if (iter > 1 && !hit_top)
  746.       say("Done.") ;
  747.    iter = 1 ;
  748. }
  749.  
  750. /*=============================================================*/
  751. /*=============================================================*/
  752.  
  753. int line_has_see_also()
  754. {
  755.    int len ;
  756.    
  757.    to_begin_line() ;
  758.    if ((len = parse_string(1,".*%([sS]ee ",NULL)) != 0)
  759.       {
  760.       point += len ;        /* go to start of cross-reference */
  761.       point += parse_string(1,"also ",NULL) ;
  762.       if (parse_string(1,"INT [0-9A-F]",NULL) ||
  763.       parse_string(1,"A[XHL] =",NULL)
  764.      )
  765.      {
  766.      point++ ;        /* move into reference */
  767.      return 1 ;
  768.      }
  769.       }
  770.    return 0 ;
  771. }
  772.  
  773. /*=============================================================*/
  774. /*=============================================================*/
  775.  
  776. int grab_int_reference(ref)
  777. char *ref ;
  778. {
  779.    int begin, start = point ;
  780.    
  781.    re_search(-1,"[, \t\n]") ;    /* backup to start of reference */
  782.    if (curchar() == '\n')    /* start of line? */
  783.       re_search(1,":[ \t]") ;    /* skip the SeeAlso: */
  784.    else if (character(point-1) == 'T' && character(point-2) == 'N')
  785.       point -= 3 ;
  786.    else
  787.       point++ ;            /* back to start of reference */
  788.    begin = point ;
  789.    re_search(1,"[,\n\"]") ;    /* find end of INT-spec */
  790.    point-- ;
  791.    if (curchar() == '\"')    /* extra string at end of INT-spec? */
  792.       {
  793.       point++ ;
  794.       re_search(1,"[\"\n]") ;    /* if yes, run to end of line or string */
  795.       }
  796.    grab(begin,point,ref) ;
  797.    point = start ;
  798.    return 0 ;
  799. }
  800.  
  801. /*=============================================================*/
  802. /*=============================================================*/
  803.  
  804. int parse_int_name(entry_name,id,extra_string)
  805. char *entry_name, *id, *extra_string ;
  806. {
  807.    int start = point ;
  808.    int i ;
  809.    char c, *last ;
  810.  
  811.    for (i = strlen(entry_name)-1 ; i >= 0 ; i--)
  812.       entry_name[i] = toupper(entry_name[i]) ;
  813.    strcpy(id,"------------") ;
  814.    if (strncmp(entry_name,"INT ",4) == 0)
  815.       {
  816.       id[0] = entry_name[4] ;
  817.       id[1] = entry_name[5] ;
  818.       entry_name += 6 ;
  819.       if (entry_name[0] == '/')
  820.      entry_name++ ;
  821.       }
  822.    else if (to_separator_line(-1))
  823.       {
  824.       id[0] = character(point+11) ;
  825.       id[1] = character(point+12) ;
  826.       }
  827.    point = start ;
  828.    c = entry_name[1] ;
  829.    if (entry_name[0] == 'A' && (c == 'X' || c == 'H' || c == 'L'))
  830.       {
  831.       entry_name += 2 ;
  832.       while (entry_name[0] == ' ' || entry_name[0] == '\t')
  833.      entry_name++ ;
  834.       if (entry_name[0] == '=')
  835.      entry_name++ ;
  836.       while (entry_name[0] == ' ' || entry_name[0] == '\t')
  837.      entry_name++ ;
  838.       if (c != 'L')
  839.      {
  840.          id[2] = entry_name[0] ;
  841.          id[3] = entry_name[1] ;
  842.      }
  843.       if (c == 'X')
  844.      {
  845.      id[4] = entry_name[2] ;
  846.      id[5] = entry_name[3] ;
  847.      entry_name += 4 ;
  848.      }
  849.       else
  850.      {
  851.      if (c == 'L')
  852.         {
  853.         id[2] = entry_name[0] ;
  854.         id[3] = entry_name[1] ;
  855.         }
  856.      entry_name += 2 ;
  857.      }
  858.       if (entry_name[0] == 'H')
  859.      entry_name++ ;
  860.       if (entry_name[0] == '/')
  861.      entry_name++ ;
  862.       }
  863.    if (index("ABCDES",entry_name[0]) && index("HILPSXF",entry_name[1]))
  864.       {
  865.       id[6] = entry_name[0] ;
  866.       c = id[7] = entry_name[1] ;
  867.       entry_name += 2 ;
  868.       while (entry_name[0] == ' ' || entry_name[0] == '\t')
  869.      entry_name++ ;
  870.       if (entry_name[0] == '=')
  871.      entry_name++ ;
  872.       while (entry_name[0] == ' ' || entry_name[0] == '\t')
  873.      entry_name++ ;
  874.       id[8] = entry_name[0] ;
  875.       id[9] = entry_name[1] ;
  876.       if (c != 'H' && c != 'L' && (c != 'F' || entry_name[2] != 'h'))
  877.      {
  878.      id[10] = entry_name[2] ;
  879.      id[11] = entry_name[3] ;
  880.      entry_name += 4 ;
  881.      }
  882.       else
  883.      entry_name += 2 ;
  884.       if (entry_name[0] == 'H')
  885.      entry_name++ ;
  886.       if (entry_name[0] == '/')
  887.      entry_name++ ;
  888.       }
  889.    if (entry_name[0] == '\"')
  890.       {
  891.       entry_name++ ;
  892.       strcpy(extra_string,entry_name) ;
  893.       last = index(extra_string,'\"') ;
  894.       if (last)
  895.      *last = '\0' ;
  896.       }
  897.    else
  898.       extra_string[0] = '\0' ;
  899.    return 0 ;
  900. }
  901.  
  902. /*=============================================================*/
  903. /*=============================================================*/
  904.  
  905. int hex2_to_int(c1,c2)
  906. char c1, c2 ;
  907. {
  908.    if (c1 >= '0' && c1 <= '9')
  909.       c1 -= '0' ;
  910.    else if (c1 >= 'A' && c1 <= 'F')
  911.       c1 = c1 - 'A' + 10 ;
  912.    else if (c1 >= 'a' && c1 <= 'f')
  913.       c1 = c1 - 'a' + 10 ;
  914.    else
  915.       return -1 ;
  916.    if (c2 >= '0' && c2 <= '9')
  917.       c2 -= '0' ;
  918.    else if (c2 >= 'A' && c2 <= 'F')
  919.       c2 = c2 - 'A' + 10 ;
  920.    else if (c2 >= 'a' && c2 <= 'f')
  921.       c2 = c2 - 'a' + 10 ;
  922.    else
  923.       return -1 ;
  924.    return 16*c1 + c2 ;
  925. }
  926.  
  927. /*=============================================================*/
  928. /*=============================================================*/
  929.  
  930. char hex_digit(val)
  931. int val ;
  932. {
  933.    if (val < 0)
  934.       return '-' ;
  935.    else
  936.       return (val > 9) ? ('A' + val - 10) : ('0' + val) ;
  937. }
  938.  
  939. /*=============================================================*/
  940. /*=============================================================*/
  941.  
  942. int scan_for_entry(entry,extra_str,first_entry)
  943. char *entry, *extra_str ;
  944. int *first_entry ;
  945. {
  946.    int bestcount = 0 ;
  947.    int bestmatch = -1 ;
  948.  
  949.    if (extra_str) extra_str = 0 ;  /* for now, to avoid compiler warning */
  950.    *first_entry = 0 ;
  951.    /* scan for the first entry for the desired interrupt number */
  952.    while (to_separator_line(1))
  953.       {
  954.       point += 2 ;
  955.       if (character(point) == entry[0] && character(point+1) == entry[1])
  956.      break ;
  957.       nl_forward() ;
  958.       }
  959.    /* now scan through the entries for the given interrupt number */
  960.    while (to_separator_line(1))
  961.       {
  962.       int i ;
  963.       char buf[14] ;
  964.       point += 2 ;
  965.       grab(point,point+12,buf) ;
  966.       if ((buf[0] != entry[0] || buf[1] != entry[1]) &&
  967.       (buf[0] != '-' && buf[1] != '-'))
  968.      break ;            /* ran out of entries... */
  969.       for (i = 2 ; i <= 12 ; i++)
  970.      {
  971.      if (buf[i] != entry[i])
  972.         break ;
  973.      }
  974.       if (i > bestcount)
  975.      {
  976.      bestcount = i ;
  977.      bestmatch = point ;
  978.      if (i > 12)
  979.         break ;            /* found an exact match */
  980.      }
  981.       nl_forward() ;
  982.       }
  983.    if (bestmatch == -1)
  984.       return 0 ;            /* we failed */
  985.    else
  986.       {
  987.       *first_entry = bestmatch ;
  988.       point = bestmatch ;        /* back to best-matching entry */
  989.       nl_forward() ;
  990.       return 1 ;            /* we were successful */
  991.       }
  992. }
  993.  
  994. /*=============================================================*/
  995. /*=============================================================*/
  996.  
  997. int goto_entry(entry_name)
  998. char *entry_name ;
  999. {
  1000.    char int_id[13], extra_string[60] ;
  1001.    int start = point, first_entry ;
  1002.    int int_num, curr_int ;
  1003.    char search_str[22] ;
  1004.    
  1005.    parse_int_name(entry_name,int_id,extra_string) ;
  1006.    int_num = hex2_to_int(int_id[0],int_id[1]) ;
  1007.    if (to_separator_line(-1))
  1008.       {
  1009.       if (character(point+11) == '-')
  1010.      curr_int = -1 ;
  1011.       else
  1012.      curr_int = hex2_to_int(character(point+11),character(point+12)) ;
  1013.       if (int_num <= 0)
  1014.      point = 0 ;        /* go to top of file */
  1015.       else
  1016.      {
  1017.      if (curr_int <= 0)
  1018.         point = 0 ;        /* go to top of file */
  1019.      strcpy(search_str,"--------.-") ;
  1020.      search_str[10] = hex_digit((int_num-1) / 16) ;
  1021.      search_str[11] = hex_digit((int_num-1) % 16) ;
  1022.      search_str[12] = '\0' ;
  1023.      if (!re_search( (int_num<=curr_int)?-1:1, search_str))
  1024.         {
  1025.         say("%s not found.",entry_name) ;
  1026.         iter = 1 ;
  1027.         return 0 ;
  1028.         }
  1029.      to_begin_line() ;
  1030.      }
  1031.       }
  1032.    else
  1033.       point = 0 ;
  1034.    if (!scan_for_entry(int_id,extra_string,&first_entry))
  1035.       {
  1036.       say("%s not found.",entry_name) ;
  1037.       if (first_entry)
  1038.      {
  1039.      mark = start ;
  1040.      point = first_entry ;
  1041.      }
  1042.       else
  1043.      point = start ;
  1044.       }
  1045.    if (has_arg)
  1046.      iter = 1 ;                /* don't search repeatedly */
  1047.    return 0 ;
  1048. }
  1049.  
  1050. /*=============================================================*/
  1051. /*=============================================================*/
  1052.  
  1053. command goto_int() on intlist_tab[FCTRL(12)]
  1054. {
  1055.    char entry_name[60], def_entry[60] ;
  1056.    int start = point ;
  1057.  
  1058.    to_begin_line() ;
  1059.    if (parse_string(1,"SeeAlso: ",NULL) != 0)
  1060.       {
  1061.       point += 9 ;        /* skip the SeeAlso: */
  1062.       if (point < start)    /* if we were originally to the right of     */
  1063.      point = start ;    /* current position, go back to original pos */
  1064.       grab_int_reference(def_entry) ;
  1065.       get_strdef(entry_name,"Goto Interrupt",def_entry) ;
  1066.       }
  1067.    else if (line_has_see_also())
  1068.       {
  1069.       grab_int_reference(def_entry) ;
  1070.       get_strdef(entry_name,"Goto Interrupt",def_entry) ;
  1071.       }
  1072.    else
  1073.       get_string(entry_name,"Goto Interrupt: ") ;
  1074.    point = start ;
  1075.    goto_entry(entry_name) ;
  1076.    if (has_arg)
  1077.       iter = 1 ;
  1078. }
  1079.  
  1080. /*=============================================================*/
  1081. /*=============================================================*/
  1082.  
  1083. void maybe_append_table_number()
  1084. {
  1085.    if (parse_string(1,".*\t%(Table ",0) == 0)
  1086.       {
  1087.       int matchsize ;
  1088.       /* if the pattern didn't match, there is no table number, */
  1089.       /* so add it */
  1090.       to_end_line() ;
  1091.       matchsize = parse_string(-1,"[ \t]+",0) ;
  1092.       if (matchsize)
  1093.      delete(point-matchsize,point) ;
  1094.       stuff("\t") ;
  1095.       insert_table_counter() ;
  1096.       }
  1097. }
  1098.  
  1099. /*=============================================================*/
  1100. /*=============================================================*/
  1101.  
  1102. void fix_unnumbered_tables()
  1103. {
  1104.    spot start = alloc_spot(1) ;
  1105.    
  1106.    *start = point ;
  1107.    point = 0 ;
  1108.    while (search(1,"\n\n"))
  1109.       {
  1110.       switch(curchar())
  1111.      {
  1112.      case 'C':
  1113.         if (parse_string(1,"Call ") != 0)
  1114.            {
  1115.            /* we got Call..., we know it doesn't have a table number */
  1116.            insert_table_counter() ;
  1117.            stuff("\n") ;
  1118.            }
  1119.         break ;
  1120.      case 'V':
  1121.         if (parse_string(1,"Values ") != 0)
  1122.            {
  1123.            /* we know this Values... doesn't have a table number */
  1124.            insert_table_counter() ;
  1125.            stuff("\n") ;
  1126.            }
  1127.         break ;
  1128.      case 'B':
  1129.         if (parse_string(1,"Bitfields ",0) == 0)
  1130.            break ;
  1131.         nl_forward() ;    /* skip to start of next line */
  1132.         maybe_append_table_number() ;
  1133.         break ;
  1134.      case 'F':
  1135.         if (parse_string(1,"Format ",0) == 0)
  1136.            break ;
  1137.         nl_forward() ;    /* skip to start of next line */
  1138.         maybe_append_table_number() ;
  1139.         break ;
  1140.      default:
  1141.         /* not a table header, so ignore it */
  1142.         break ;
  1143.      }
  1144.       }
  1145.    point = *start ;
  1146.    free_spot(start) ;
  1147. }
  1148.  
  1149. /*=============================================================*/
  1150. /*=============================================================*/
  1151.  
  1152. short *gather_table_numbers(new_numbers)
  1153. short *new_numbers ;
  1154. {
  1155.    int tcount[6] ;
  1156.    char counter[5] ;
  1157.    int old_number ;
  1158.    int table_type ;
  1159.    spot start = alloc_spot(1) ;
  1160.    save_var case_fold = 0 ;
  1161.    
  1162.    tcount[0] = tcount[1] = tcount[2] = tcount[3] = tcount[4] = tcount[5] = 0 ;
  1163.    *start = point ;
  1164.    point = 0 ;
  1165.    while (search(1,"(Table "))
  1166.       {
  1167.       char *tbl ;
  1168.       int table_offset ;
  1169.       grab(point,point+4,counter) ;
  1170.       tbl = index(table_ID_letters,counter[0]) ;
  1171.       if (tbl)
  1172.      table_offset = (tbl-table_ID_letters) ;
  1173.       else
  1174.      table_offset = 0 ;
  1175.       old_number = strtoi(counter+1,10) + 1000*table_offset ;
  1176.       table_type = (table_offset > 9) ? (table_offset-9) : 0 ;
  1177.       new_numbers[old_number] = (short)++(tcount[table_type]) ;
  1178.       }
  1179.    point = *start ;
  1180.    free_spot(start) ;
  1181.    return new_numbers ;
  1182. }
  1183.  
  1184. /*=============================================================*/
  1185. /*=============================================================*/
  1186.  
  1187. int adjust_table_numbers(new_numbers, dangling)
  1188. short *new_numbers ;
  1189. int dangling ;
  1190. {
  1191.    char counter[5] ;
  1192.    int old_number ;
  1193.    int old_type ;
  1194.    char *tbl ;
  1195.    int table_offset ;
  1196.    spot start = alloc_spot(1) ;
  1197.    
  1198.    *start = point ;
  1199.    point = 0 ;
  1200.    while (search(1,"(Table "))
  1201.       {
  1202.       grab(point,point+4,counter) ;
  1203.       tbl = index(table_ID_letters,counter[0]) ;
  1204.       if (tbl)
  1205.      table_offset = 1000*(tbl-table_ID_letters) ;
  1206.       else
  1207.      table_offset = 0 ;
  1208.       old_number = strtoi(counter+1,10) + table_offset ;
  1209.       old_type = (counter[0] >= '0' && counter[0] <= '9') ? 0 : counter[0] ;
  1210.       if (old_number > 0)
  1211.      {
  1212.      delete(point,point+4) ;
  1213.      if (old_type)
  1214.         bprintf("%c%03d",old_type,new_numbers[old_number]%1000) ;
  1215.      else
  1216.         bprintf("%04d",new_numbers[old_number]) ;
  1217.      }
  1218.       }
  1219.    point = 0 ;
  1220.    while (re_search(1,"[, \t]%#[0-9CFMPR][0-9][0-9][0-9]"))
  1221.       {
  1222.       grab(point-4,point,counter) ;
  1223.       tbl = index(table_ID_letters,counter[0]) ;
  1224.       if (tbl)
  1225.      table_offset = 1000*(tbl-table_ID_letters) ;
  1226.       else
  1227.      table_offset = 0 ;
  1228.       old_number = strtoi(counter+1,10) + table_offset ;
  1229.       old_type = (counter[0] >= '0' && counter[0] <= '9') ? 0 : counter[0] ;
  1230.       if (old_number > 0)
  1231.      {
  1232.      if (new_numbers[old_number])
  1233.         {
  1234.         delete(point-4,point) ;
  1235.         if (old_type)
  1236.            bprintf("%c%03d",old_type,new_numbers[old_number]) ;
  1237.         else
  1238.            bprintf("%04d",new_numbers[old_number]) ;
  1239.         }
  1240.      else /* dangling xref */
  1241.         {
  1242.         dangling++ ;
  1243.         point -= 4 ;
  1244.         stuff("?") ;
  1245.         point += 4 ;
  1246.         }
  1247.      }
  1248.       }
  1249.    point = *start ;
  1250.    free_spot(start) ;
  1251.    return dangling ;
  1252. }
  1253.  
  1254. /*=============================================================*/
  1255. /*=============================================================*/
  1256.  
  1257. int get_list_file(list_file)
  1258. char *list_file ;
  1259. {
  1260.    char abs_filename[FNAMELEN] ;
  1261.    strcpy(abs_filename,list_file) ;
  1262.    absolute(abs_filename) ;
  1263.    return find_it(abs_filename,1) ;
  1264. }
  1265.  
  1266. /*=============================================================*/
  1267. /*=============================================================*/
  1268.  
  1269. command renumber_tables()
  1270. {
  1271.    short *new_numbers ;
  1272.    int num_tables ;
  1273.    int dangling ;
  1274.    int i ;
  1275.    
  1276.    for (i = 0 ; list_files[i] ; i++)
  1277.       {
  1278.       if (get_list_file(list_files[i]) == 0)
  1279.      {
  1280.      say("Renumber Pass 1: numbering unnumbered tables (%s)",
  1281.          list_files[i]) ;
  1282.      fix_unnumbered_tables() ;
  1283.      }
  1284.       else
  1285.      say("Renumber Pass 1: forced to skip %s") ;
  1286.       }
  1287.    num_tables = 1000*strlen(table_ID_letters) ;
  1288.    new_numbers = (short*)malloc(num_tables*sizeof(short)) ;
  1289.    if (!new_numbers)
  1290.       {
  1291.       say("Out of memory!") ;
  1292.       return ;
  1293.       }
  1294.    for (i = 0 ; i < num_tables ; i++)
  1295.       new_numbers[i] = 0 ;
  1296.    for (i = 0 ; list_files[i] ; i++)
  1297.       {
  1298.       if (get_list_file(list_files[i]) == 0)
  1299.      {
  1300.      say("Renumber Pass 2: gathering table numbers (%s)",
  1301.          list_files[i]) ;
  1302.      gather_table_numbers(new_numbers) ;
  1303.      }
  1304.       else
  1305.      say("Renumber Pass 2: forced to skip %s") ;
  1306.       }
  1307.    dangling = 0 ;
  1308.    for (i = 0 ; list_files[i] ; i++)
  1309.       {
  1310.       if (get_list_file(list_files[i]) == 0)
  1311.      {
  1312.      say("Renumber Pass 3: adjusting table numbers (%s)",
  1313.          list_files[i]) ;
  1314.      dangling = adjust_table_numbers(new_numbers,dangling) ;
  1315.      }
  1316.       else
  1317.      say("Renumber Pass 3: forced to skip %s") ;
  1318.       }
  1319.    free(new_numbers) ;
  1320.    if (dangling)
  1321.       say("%d dangling cross-references, search for '#?'",dangling) ;
  1322.    else
  1323.       say("Done") ;
  1324. }
  1325.  
  1326. /*=============================================================*/
  1327. /*=============================================================*/
  1328.  
  1329. command make_distribution()
  1330. {
  1331.    int i ;
  1332.    
  1333.    for (i = 0 ; list_files[i] ; i++)
  1334.       {
  1335.       /* switch to proper buffer, or load if not yet in a buffer */
  1336.       if (get_list_file(list_files[i]) == 0)
  1337.      {
  1338.      say("Setting divider lines (%s)",list_files[i]) ;
  1339.      point = size() ;
  1340.      while (point > 0)
  1341.         if (!number_one_int())
  1342.            break ;
  1343.      }
  1344.       else
  1345.      say("Forced to skip %s !",list_files[i]) ;
  1346.       }
  1347.    for (i = 0 ; list_files[i] ; i++)
  1348.       {
  1349.       /* switch to proper buffer, or load if not yet in a buffer */
  1350.       if (get_list_file(list_files[i]) == 0)
  1351.      {
  1352.      say("Tabifying file (%s)",list_files[i]) ;
  1353.      mark = 0 ;
  1354.      point = size() ;
  1355.      tabify_region() ;
  1356.      }
  1357.       }
  1358.    renumber_tables() ;
  1359.    save_all_buffers() ;
  1360.    say("Ready for distribution") ;
  1361.    point = 0 ;
  1362.    /* !!! should also split main list automatically */
  1363. }
  1364.  
  1365. /*=============================================================*/
  1366. /*=============================================================*/
  1367.  
  1368. void find_table_counter()
  1369. {
  1370.    save_var point = (size() > 10000) ? size() - 10000 : 0 ;
  1371.  
  1372.    search(1,"Highest Table Number = ") ;
  1373.    table_counter = alloc_spot(1) ;
  1374. }
  1375.  
  1376. /*=============================================================*/
  1377. /*  Coloring functions for Epsilon v7.0+               */
  1378. /*=============================================================*/
  1379.  
  1380. #if EELVERSION >= 70
  1381. int int_recolor_range(from, to)
  1382. int from, to ;
  1383. {
  1384.    if (from >= to)
  1385.       return to ;
  1386.    set_character_color(from,to,-1) ;
  1387.    save_var point, matchstart, matchend ;
  1388.    point = from ;
  1389.    if (to > size())
  1390.       to = size() ;
  1391.    while (point < to)
  1392.       {
  1393.       int start = point ;
  1394.       int len ;
  1395.       if (curchar() >= 'A' && curchar() <= 'V')
  1396.      {
  1397.      if (parse_string(1,table_headers,NULL) != 0)
  1398.         {
  1399.         nl_forward() ;
  1400.         point-- ;
  1401.         set_character_color(start,point,color_class c_comment) ;
  1402.         }
  1403.      else if ((len = parse_string(1,all_sections,NULL)) > 0)
  1404.         set_character_color(start,start+len,color_class c_function) ;
  1405.      }
  1406.       else if (curchar() == '\t' &&
  1407.            (len = parse_string(1,indented_sections,NULL)) != 0)
  1408.      {
  1409.      while (curchar() == '\t')
  1410.         {
  1411.         point++ ;
  1412.         len-- ;
  1413.         }
  1414.      set_character_color(point,point+len,color_class c_function) ;
  1415.      }
  1416.       nl_forward() ;
  1417.       }
  1418.    return point ;
  1419. }
  1420. #endif /* Epsilon v7.0+ */
  1421.  
  1422. #if EELVERSION >= 70
  1423. int int_recolor_from_here(safe)
  1424. int safe ;
  1425. {
  1426.    save_var point ;
  1427.    if (safe != point)
  1428.       {
  1429.       to_begin_line() ;            /* start of line is always 'safe' */
  1430.       }
  1431.    return point ;
  1432. }
  1433. #endif /* Epsilon v7.0+ */
  1434.  
  1435. /*=============================================================*/
  1436. /* Put the current buffer into IntList major mode           */
  1437. /*=============================================================*/
  1438.  
  1439. command intlist_mode()
  1440. {
  1441.    mode_keys = intlist_tab ;
  1442.    intlist_tab[')'] = intlist_tab[']'] = (short) show_matching_delimiter;
  1443.    delete_hacking_tabs = 0 ;
  1444.    major_mode = strsave("IntList") ;
  1445.    auto_indent = 0 ;
  1446.    margin_right = 79 ;
  1447.    want_backups = 1 ;
  1448.    undo_size = 200000 ;     /* less than default 500,000 since list is so big */
  1449.    find_table_counter() ;
  1450. #if EELVERSION >= 70
  1451.    recolor_range = int_recolor_range ;
  1452.    recolor_from_here = int_recolor_from_here ;
  1453.    if (want_code_coloring)
  1454.       when_setting_want_code_coloring() ;
  1455. #endif /* Epsilon v7.0+ */
  1456.    make_mode() ;
  1457. }
  1458.  
  1459. when_loading()
  1460. {
  1461.    char *curbuf ;
  1462.    int i ;
  1463.    
  1464.    want_backups = want_backups.default = 1 ;
  1465.    strcpy(backup_name,"%pbak/%b%e") ;        /* put backups in BAK subdir */
  1466.    one_window() ;
  1467.    intlist_mode() ;
  1468.    if (exist("interrup.1st"))
  1469.       {
  1470.       curbuf = bufname ;
  1471.       bufname = "interrup.1st" ;
  1472.       intlist_mode() ;
  1473.       want_code_coloring = 0 ;
  1474.       when_setting_want_code_coloring() ;
  1475.       bufname = curbuf ;
  1476.       }
  1477.    for (i = 0 ; list_files[i] ; i++)
  1478.       {
  1479.       if (exist(list_files[i]))
  1480.      {
  1481.      curbuf = bufname ;
  1482.      bufname = list_files[i] ;
  1483.      intlist_mode() ;
  1484.      bufname = curbuf ;
  1485.      }
  1486.       }
  1487. #if EELVERSION >= 70
  1488.    strcpy(mode_end," %d%p%S%>C%c") ;
  1489. #endif /* Epsilon v7.0+ */
  1490. #if EELVERSION >= 60 && EELVERSION < 70
  1491.    strcpy(mode_end," %d%p%S") ;
  1492. #endif /* Epsilon v6.x */
  1493. }
  1494.  
  1495. /*=============================================================*/
  1496. /* automagically switch into interrupt list mode on .LST and .1ST files */
  1497.  
  1498. suffix_lst()   { intlist_mode(); }
  1499. suffix_1st()   { intlist_mode(); }
  1500.  
  1501. /* end of file intlist.e */
  1502.